package com.tencent.sr.iris.activity.service.event.task;

import com.alibaba.fastjson.JSON;
import com.google.common.collect.Lists;
import com.tencent.sr.iris.activity.common.enums.AwardRecordIssueStatusEnum;
import com.tencent.sr.iris.activity.common.enums.TaskRecordAwardIssueStatusEnum;
import com.tencent.sr.iris.activity.common.enums.UserTaskStatusEnum;
import com.tencent.sr.iris.activity.common.util.ShardingIdUtil;
import com.tencent.sr.iris.activity.domain.event.dto.ActivityDTO;
import com.tencent.sr.iris.activity.domain.event.dto.ActivityTaskDTO;
import com.tencent.sr.iris.activity.interfaces.event.dto.ActivityEventDTO;
import com.tencent.sr.iris.activity.repository.entity.TIrisActivityAwardRecordDO;
import com.tencent.sr.iris.activity.repository.entity.TIrisUserTaskRecordDO;
import com.tencent.sr.iris.activity.repository.mapper.TIrisActivityAwardRecordMapper;
import com.tencent.sr.iris.activity.repository.mapper.example.TIrisActivityAwardRecordExample;
import com.tencent.sr.iris.activity.service.activity.ActivityCommonService;
import com.tencent.sr.iris.activity.service.activity.IrisActivityAwardRecordService;
import com.tencent.sr.iris.activity.service.activity.IrisUserTaskRecordService;
import com.tencent.sr.iris.activity.service.event.vo.BaseUserTaskDataVO;
import com.tencent.sr.iris.activity.service.event.vo.TaskExecutorExtendInfo;
import java.time.LocalDate;
import java.time.LocalDateTime;
import java.util.Calendar;
import java.util.Date;
import java.util.List;
import java.util.Objects;
import javax.annotation.Resource;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.collections4.CollectionUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

@Slf4j
@Component
public class UserBecomeTraineeTaskExecutor extends AbstractIrisTaskExecutor {

    @Autowired
    private IrisUserTaskRecordService userTaskRecordService;

    @Autowired
    private ActivityCommonService activityCommonService;

    @Resource
    private
    IrisActivityAwardRecordService irisActivityAwardRecordService;

    @Override
    public void process(ActivityEventDTO msg, ActivityDTO activity, ActivityTaskDTO task,
            List<String> eventHandingInfoList, TaskExecutorExtendInfo taskExecutorExtendInfo) {
        //查询任务完成进度
        String period = LocalDate.now().toString();
        TIrisUserTaskRecordDO userTaskRecordDO = queryUserTaskRecord(msg.getUid(), activity.getBizId(),
                task.getBizId(), period);
        log.info("注册有礼用户成为见习事件处理，当前任务完成进度:{}", JSON.toJSONString(userTaskRecordDO));
        if (Objects.nonNull(userTaskRecordDO)) {
            if (UserTaskStatusEnum.FINISHED.getCode() == userTaskRecordDO
                    .getUserTaskStatus()) {
                eventHandingInfoList.add("注册有礼，下级用户已完成任务");
                //已完成任务
                log.info("注册有礼，下级用户已完成任务,uid:{},ActivityEventDTO:{},", msg.getUid(),
                        JSON.toJSONString(msg));
                return;
            }

        } else {
            //新增用户活动任务完成进度
            userTaskRecordDO = buildUserTaskRecordDO(activity, task, msg);
            eventHandingInfoList.add("注册有礼任务达成");
            log.info("注册有礼任务达成,uid:{},ActivityEventDTO:{}", msg.getUid(),
                    JSON.toJSONString(msg));
        }

        executeAward(task, eventHandingInfoList, userTaskRecordDO);

    }

    /**
     * 执行发奖流程
     *
     * @param task
     * @param eventHandingInfoList
     * @param userTaskRecordDO
     */
    public void executeAward(ActivityTaskDTO task, List<String> eventHandingInfoList,
            TIrisUserTaskRecordDO userTaskRecordDO) {
        //判断用户当前是否已经发过奖
        //如果当天已经发过奖，不再调用发奖接口
        String uid = userTaskRecordDO.getUid();
        String taskId = userTaskRecordDO.getTaskId();
        String taskPeriod = userTaskRecordDO.getTaskPeriod();

        Date date = new Date();
        Date startDate = formatStartTime(date);
        Date endDate = formatEndTime(date);
        List<TIrisActivityAwardRecordDO> list = irisActivityAwardRecordService.queryIssueList(
                userTaskRecordDO.getActivityId(), taskId, uid, startDate, endDate);

        TIrisActivityAwardRecordDO awardRecordDO = null;
        if (CollectionUtils.isNotEmpty(list)) {
            eventHandingInfoList.add("注册有礼今日已发过奖，不在调用发奖接口，直接返回成功");
        } else {
            //发放权益
            awardRecordDO = activityCommonService.sendAward(userTaskRecordDO, task);
            if (awardRecordDO != null
                    && AwardRecordIssueStatusEnum.ISSUE_SUCCEED.getCode() == awardRecordDO.getIssueStatus()) {
                eventHandingInfoList.add("任务发奖成功");
                //设置发奖标识
                LocalDateTime awardTagExpiredTime = LocalDateTime.now().withHour(23).withMinute(59).withSecond(59);
                irisActivityAwardRecordService
                        .setAwardTimeToday(userTaskRecordDO.getTaskId(), uid, taskPeriod, awardTagExpiredTime);
            } else {
                eventHandingInfoList.add("任务发奖失败");
            }

        }

        //记录任务进度
        userTaskRecordService.updateUserTaskRecordStatus(userTaskRecordDO, awardRecordDO);
    }


    @Override
    public void fillTaskRecordStatus(ActivityEventDTO eventDTO, ActivityDTO act, ActivityTaskDTO task,
            TIrisUserTaskRecordDO userTaskRecordDO, LocalDate currentLocalDate) {
    }


    @Override
    public boolean executeAward(ActivityEventDTO event, ActivityDTO act, ActivityTaskDTO task) {
        return false;
    }

    @Override
    public boolean checkTaskThreshold(ActivityEventDTO event, ActivityDTO act, ActivityTaskDTO task,
            BaseUserTaskDataVO userTaskDataVO) {
        return false;
    }

    @Override
    public BaseUserTaskDataVO prepareUserTaskData(ActivityEventDTO event, ActivityDTO act, ActivityTaskDTO task) {
        return null;
    }

    private static Date formatStartTime(Date date) {
        Calendar instance = Calendar.getInstance();
        instance.setTime(date);
        instance.set(Calendar.HOUR_OF_DAY, 0);
        instance.set(Calendar.MINUTE, 0);
        instance.set(Calendar.SECOND, 0);
        return instance.getTime();
    }

    private static Date formatEndTime(Date date) {
        Calendar instance = Calendar.getInstance();
        instance.setTime(date);
        instance.set(Calendar.HOUR_OF_DAY, 23);
        instance.set(Calendar.MINUTE, 59);
        instance.set(Calendar.SECOND, 59);
        return instance.getTime();
    }
}
